/*** 通用应用 Web 服务启动脚本 */
const express = require('express')
const Vue = require('vue')
const { createBundleRenderer } = require('vue-server-renderer')
const fs = require('fs')
const setupDevServer = require('./build/setup-dev-server')
// 创建一个 express 实例 
const app = express()

app.use('/dist', express.static('./dist'))

const isProd = process.env.NODE_ENV === 'production'

let renderer
let onReady
if (isProd) {
  const serverBundle = require('./dist/vue-ssr-server-bundle.json')
  const clientManifest = require('./dist/vue-ssr-client-manifest.json')
  const template = fs.readFileSync('./index.template.html', 'utf-8')
  // 生成一个渲染器
  renderer = createBundleRenderer(serverBundle, {
    // 渲染器就会自动把渲染的结果注入到模板中 
    template,
    clientManifest
  })
} else {
  // 开发模式 -> 监视打包构建 -> 重新生成 renderer 渲染器
  onReady = setupDevServer(app, (serverBundle, template, clientManifest) => {
    // 基于重新打包的结果生成新的 renderer
    renderer = createBundleRenderer(serverBundle, {
      // 渲染器就会自动把渲染的结果注入到模板中 
      template,
      clientManifest
    })
  })
}



const render = async (req, res) => {
  try {
    const html = await renderer.renderToString({
      title: 'SSR',
      meta: ` <meta name="description" content="hello world"> `,
      url: req.url
    })
    res.setHeader('Content-Type', 'text/html; charset=utf8')
    res.end(html)
  } catch (error) {
    res.status(500).end('Internal Server Error.')
  }
}

// 服务端设置为*，意味着所有的路由都会进入这里
app.get('*', isProd
  ? render
  : async (req, res) => {
    // 等待有了 Renderer 渲染器以后，调用 render 渲染
    await onReady
    render(req, res)
  }
)
// 监听端口，启动 Web 服务
app.listen(3000, () => {
  console.log('running at port 3000.')
})